import 'package:flutter/widgets.dart';
import 'package:imperius_insights/entity/bugstats.dart';
import 'package:imperius_insights/modules/projects/viewmodels/project.dart';
import 'package:imperius_insights/portal/state/indicator/indicator.dart';
import 'package:imperius_insights/portal/state/mobx/store.dart';
import 'package:mobx/mobx.dart';
import 'package:table_calendar/table_calendar.dart';

import 'domain.dart';

part 'view_model.g.dart';

class ViewModel = _ViewModelInternal with _$ViewModel;

abstract class _ViewModelInternal with Store, StoreWithLifecycle {
  Domain _domain;
  final String pmo;

  @observable
  IndicatorState<ProjectViewModel> project;
  @observable
  IndicatorState<IssuesClassification> issuesClassification;

  @observable
  Map<DateTime, List> calendarEvents;

  CalendarController _calendarController;

  CalendarController get calendarController => _calendarController;

  _ViewModelInternal({ this.pmo }) {
    _domain = Domain(pmo: pmo);
  }


  @override
  onContextAttached(BuildContext context) {
    super.onContextAttached(context);
    _calendarController = CalendarController();
    project = IndicatorState<ProjectViewModel>();
    issuesClassification = IndicatorState<IssuesClassification>();
    refresh();
  }

  refresh() async {
    project.setStatus(status: Status.loading);
    issuesClassification.setStatus(status: Status.loading);
    await project.fireFetch(() async {
      final project = await _domain.fetchProjectBasalInfo();
      final projectVm = ProjectViewModel(project);
      onProjectTaped(projectVm);
      return projectVm;
    });
    await issuesClassification.fireFetch(_domain.fetchIssues);
  }

  @action
  void onProjectTaped(ProjectViewModel projectVm) {
    final today = DateTime.now();
    final project = projectVm.data;
    if (today.isAfter(project.startDevDate) &&
        (project.scheduledPublishDate != null &&
            today.isBefore(project.scheduledPublishDate))) {
      _calendarController.setFocusedDay(today);
    } else {
      _calendarController.setFocusedDay(project.startDevDate);
    }

    final putEventWorkday = (DateTime date) {
      if (date.weekday == DateTime.saturday || date.weekday == DateTime.sunday) {
        return;
      }
      calendarEvents[date] = [project.pmo];
    };

    calendarEvents = Map<DateTime, List>();
    if (project.startDevDate != null && project.endDevDate != null) {
      for (DateTime cursor = project.startDevDate;
      cursor.isBefore(project.endDevDate) || cursor == project.endDevDate;
      cursor = cursor.add(Duration(days: 1))) {
        putEventWorkday(cursor);
      }
    }

    if (project.startTestDate != null && project.endTestDate != null) {
      for (DateTime cursor = project.startTestDate;
      cursor.isBefore(project.endTestDate) || cursor == project.endTestDate;
      cursor = cursor.add(Duration(days: 1))) {
        putEventWorkday(cursor);
      }
    }

    if (project.scheduledPublishDate != null) {
      putEventWorkday(project.scheduledPublishDate);
    }
  }

  @override
  onContextDetached(BuildContext context) {
    _calendarController.dispose();
    super.onContextDetached(context);
  }
}
